package pimp.organizermanager;

import pimp.*;
import java.util.*;

public class StandardCalendar extends OurCalendar {
    private HashMap<Integer, Year> years;

    private static class Singleton {
        private final static StandardCalendar instance = new StandardCalendar();
    }

    private StandardCalendar() {
        years = new HashMap<Integer,Year>();
        System.out.println("StandardCalendar initialization completed!");
    }

    public static StandardCalendar getInstance() {
        return Singleton.instance;
    }

    public boolean checkOrder(Date beginDate, Date endDate) {
        int beginYear = beginDate.getThisYear();
        int endYear = endDate.getThisYear();
        int beginMonth = beginDate.getThisMonth();
        int endMonth = endDate.getThisMonth();
        int beginDay = beginDate.getThisDay();
        int endDay = endDate.getThisDay();

        if(beginYear > endYear) {
            return false;
        }

        if(beginYear == endYear) {
            if(beginMonth > endMonth) {
                return false;
            }
            if(beginMonth != 0 && (beginDay > endDay)) {
                return false;
            }
        }
        return true;
    }

    public boolean addEvent(Event event, Date beginDate, Date endDate) {
        int beginYear = beginDate.getThisYear();
        int endYear = endDate.getThisYear();
        int beginMonth = (beginDate.getThisMonth());
        int endMonth = (endDate.getThisMonth());
        int beginDay = beginDate.getThisDay();
        int endDay = endDate.getThisDay();

        if(beginYear < 1900 || endYear < 1900) {
            return false;
        }

        if(beginMonth < 0 || beginMonth > 12 || endMonth < 0 || endMonth > 12 ||
                (beginMonth == 0 && endMonth!=0) || (beginMonth !=0 && endMonth == 0)) {
            return false;
        }

        if((beginMonth != 0) && (beginDay < 0 || endDay < 0 || (beginDay == 0 &&
                endDay != 0) || (beginDay != 0 && endDay == 0))) {
            return false;
        }

        if(beginMonth != 0 && beginDay != 0 && endDay != 0) {
            if((calculateDate(beginDate) && calculateDate(endDate)) == false) {
                return false;
            }
        }

        if(checkOrder(beginDate, endDate) == false) {
            return false;
        }
        Year year;
        for(int i = beginYear; i <= endYear; ++i) {
            if(years.get(i) ==  null) {
                years.put(i, new Year(i));
            }
            year = years.get(i);
            if(year.addEvent(event, beginDate, endDate) == false) {
               return false;
            }
        }
        return true;
    }

    @Override
    public Map<ID,GlobalEvent> getGlobalEventByDate(Date beginDate, Date endDate) {
        Map<ID, GlobalEvent> map = new HashMap<ID, GlobalEvent>();
        int beginYear = beginDate.getThisYear();
        int endYear = endDate.getThisYear();
        for(int i = beginYear; i <= endYear; ++i) {
            Year year = years.get(i);
            if(year != null) {
                year.getGlobalEventByDate(beginDate, endDate, map);
            }
        }
        return map;
    }

    @Override
    public Map<ID, GlobalEvent> getGlobalEventByDate(Date beginDate, Date endDate,
            ID id) {
        throw new UnsupportedOperationException("Not supported yet.");
    }

}
